package com.lujianfei.powersearch.ui.subitem.viewmodel

import androidx.databinding.ObservableArrayList
import androidx.databinding.ObservableBoolean
import androidx.databinding.ObservableField
import androidx.lifecycle.ViewModel
import androidx.lifecycle.viewModelScope
import com.lujianfei.powersearch.database.SearchItemModel
import com.lujianfei.powersearch.utils.DatabindingDiffUtils
import com.orm.SugarRecord
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext

class SubItemViewModel : ViewModel() {

    val data = ObservableArrayList<SearchItemModel>()

    var searchItemModel: SearchItemModel? = null
    var searchItemModelFromLongClick: SearchItemModel? = null

    var onItemClickCallback: ((SearchItemModel) -> Unit)? = null
    val onItemClick: ((SearchItemModel) -> Unit) = {
        onItemClickCallback?.invoke(it)
    }
    var onItemLongClickCallback: ((SearchItemModel) -> Unit)? = null
    val onItemLongClick: ((SearchItemModel) -> Unit) = {
        onItemLongClickCallback?.invoke(it)
    }

    val loading = ObservableBoolean(false)

    fun loadData() {
        loading.set(true)
        viewModelScope.launch {
            val resp = withContext(Dispatchers.IO) {
                val searchItemModels = SugarRecord.find(
                    SearchItemModel::class.java,
                    "parentId=? order by name",
                    "" + searchItemModel?.id
                )
                searchItemModels.sortByDescending { it.sort }
                searchItemModels.forEach {
                    updateSubCount(it)
                    updateCost(it)
                    updateTimeStampObservableField(it)
                }
                searchItemModels
            }
            loading.set(false)
            DatabindingDiffUtils.setData(oldList = data, newList = resp)
        }
    }

    private fun updateSubCount(item: SearchItemModel?) {
        if (item == null) {
            return
        }
        val sublist = SugarRecord.find(SearchItemModel::class.java, "parentId=?", "" + item.id)
        item?.subCount = sublist.size
    }

    private fun updateCost(item: SearchItemModel) {
        val childList = SugarRecord.find(SearchItemModel::class.java, "parentId=?", "" + item.id)
        if (childList == null || childList.isEmpty()) {
            return
        } else {
            runCatching {
                val childSum =
                    childList.sumOf { if (it.cost.isNullOrBlank()) 0.0 else it.cost!!.toDouble() }
                if (childSum > 0.0) {
                    item.cost = childSum.toString()
                    item.save()
                }
            }
            childList.forEach {
                updateCost(it)
            }
        }
    }

    fun moveTo(moveToModel: SearchItemModel) {
        searchItemModelFromLongClick?.parentId = moveToModel.id
        searchItemModelFromLongClick?.save()
        loadData()
    }

    fun updateCountDown() {
        viewModelScope.launch(Dispatchers.Main) {
            data.forEach {
                updateTimeStampObservableField(it)
            }
        }
    }

    private fun updateTimeStampObservableField(it: SearchItemModel) {
        if (it.startTime == 0L) {
            if (it.countDownStart == null) {
                it.countDownStart = ObservableField("")
            }
            it.countDownStart?.set("")
        } else {
            getCountDown(timeStamp = it.startTime) { day: Int, hour: Int, minute: Int, second: Int ->
                if (it.countDownStart == null) {
                    it.countDownStart = ObservableField("")
                }
                it.countDownStart?.set(
                    getCountDownSimpleStr(
                        day = day,
                        hour = hour,
                        minute = minute,
                        second = second
                    )
                )
            }
        }
        if (it.endTime == 0L) {
            if (it.countDownEnd == null) {
                it.countDownEnd = ObservableField("")
            }
            it.countDownEnd?.set("")
        } else {
            getCountDown(timeStamp = it.endTime) { day: Int, hour: Int, minute: Int, second: Int ->
                if (it.countDownEnd == null) {
                    it.countDownEnd = ObservableField("")
                }
                it.countDownEnd?.set(
                    getCountDownSimpleStr(
                        day = day,
                        hour = hour,
                        minute = minute,
                        second = second
                    )
                )
            }
        }
    }

    private fun getCountDownSimpleStr(day: Int, hour: Int, minute: Int, second: Int): String {
        if (day == 0) {
            return if (hour == 0) {
                if (minute == 0) {
                    if (second > 0) {
                        "还剩${second}秒"
                    } else {
                        "已过"
                    }
                } else {
                    "还剩${minute}分${second}秒"
                }
            } else {
                "还剩${hour}小时${minute}分${second}秒"
            }
        } else {
            return "还剩${day}天${hour}小时${minute}分${second}秒"
        }
    }

    private fun getCountDown(
        timeStamp: Long,
        callback: (day: Int, hour: Int, minute: Int, second: Int) -> Unit
    ) {
        val duration = timeStamp - System.currentTimeMillis() / 1000
        var day = 0
        var hour = 0
        var minute = 0
        var second = duration
        if (second >= 60) {
            minute = (second / 60).toInt()
            second %= 60
        }
        if (minute >= 60) {
            hour = (minute / 60)
            minute %= 60
        }
        if (hour >= 24) {
            day = (hour / 24)
            hour %= 24
        }
        callback.invoke(day, hour, minute, second.toInt())
    }

    fun getParent(): SearchItemModel? {
        return SugarRecord.findById(SearchItemModel::class.java, searchItemModel?.parentId)
    }
}